/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */

package z.h.w.jar.data.time;

import java.text.SimpleDateFormat;
import java.util.Calendar;
import java.util.Map;
import java.util.Map.Entry;
import java.util.Set;
import z.h.w.jar.data.time.period.Period;
import z.h.w.jar.kit.method.Insieme;
import z.h.w.jar.kit.method.Num;
import z.h.w.jar.kit.method.Text;

/**
 *
 * @author EnzoZhong
 */
public class AttrAct {

      private SimpleDateFormat simpleDateFormat = new SimpleDateFormat ();

      public AttrAct () {
      }

      public String getFieldLocale ( Time date , Attr attr ) {
            switch ( attr ) {
                  case CENTURY: {
                        simpleDateFormat.applyPattern ( "yyyy" );
                        String strYear = simpleDateFormat.format ( date ).substring ( 0 , 2 );
                        Integer intYear = Integer.parseInt ( strYear ) + 1;
                        return String.valueOf ( intYear ) + "st";
                  }
                  case DAY: {
                        simpleDateFormat.applyPattern ( "dd" );
                        return simpleDateFormat.format ( date );
                  }
                  case EANPN: {
                        return mapGet ( date , Attr.eanpnMap , "HHmm" );
                  }
                  case ERA: {
                        String strEra = date.tell ( Attr.YEAR ).substring ( 2 , 3 );
                        Integer intEra = Integer.parseInt ( strEra );
                        return String.valueOf ( intEra ) + "0s";
                  }
                  case HOROSCOPE: {
                        return mapGet ( date , Attr.horoscopeMap , "MMdd" );
                  }
                  case HOUR: {
                        simpleDateFormat.applyPattern ( "HH" );
                        return simpleDateFormat.format ( date );
                  }
                  case MILLISECOND: {
                        simpleDateFormat.applyPattern ( "SSS" );
                        return simpleDateFormat.format ( date );
                  }
                  case MINUTE: {
                        simpleDateFormat.applyPattern ( "mm" );
                        return simpleDateFormat.format ( date );
                  }
                  case MONTH: {
                        return createCalendarMap ( date , Calendar.MONTH );
                  }
                  case SEASON: {
                        return mapGet ( date , Attr.seasonMAP , "MMdd" );
                  }
                  case SECOND: {
                        simpleDateFormat.applyPattern ( "ss" );
                        return simpleDateFormat.format ( date );
                  }
                  case WEEK: {
                        return createCalendarMap ( date , Calendar.DAY_OF_WEEK );
                  }
                  case YEAR: {
                        simpleDateFormat.applyPattern ( "yyyy" );
                        return simpleDateFormat.format ( date );
                  }
                  case ZODIAC: {
                        simpleDateFormat.applyPattern ( "yyyy" );
                        Double year = Double.parseDouble ( simpleDateFormat.format ( date ) );
                        return Attr.lunarMap.get ( year % 12 );
                  }
            }
            return null;
      }

      private String createCalendarMap ( Time date , Integer type ) {
            Calendar calendar = Calendar.getInstance ();
            calendar.setTime ( date );
            Integer num = calendar.get ( type );
            Map<String , Integer> names = calendar.getDisplayNames ( type , Calendar.SHORT , date.getLocale () );
            Map<Integer , String> map = Insieme.swop ( names );
            Set<Entry<Integer , String>> set = map.entrySet ();
            for ( Entry<Integer , String> entry : set ) {
                  Integer key = entry.getKey ();
                  String valu = entry.getValue ();
                  map.put ( key , Text.firstUpper ( valu ) );
            }
            return map.get ( num );
      }

      public String getField ( Time date , Attr attr ) {
            switch ( attr ) {
                  case CENTURY: {
                        simpleDateFormat.applyPattern ( "yyyy" );
                        String strYear = simpleDateFormat.format ( date ).substring ( 0 , 2 );
                        Integer intYear = Integer.parseInt ( strYear ) + 1;
                        return String.valueOf ( intYear ) + "st";
                  }
                  case DAY: {
                        simpleDateFormat.applyPattern ( "dd" );
                        return simpleDateFormat.format ( date );
                  }
                  case EANPN: {
                        return mapGet ( date , Attr.eanpnMap , "HHmm" );
                  }
                  case ERA: {
                        String strEra = date.tell ( Attr.YEAR ).substring ( 2 , 3 );
                        Integer intEra = Integer.parseInt ( strEra );
                        return String.valueOf ( intEra ) + "0s";
                  }
                  case HOROSCOPE: {
                        return mapGet ( date , Attr.horoscopeMap , "MMdd" );
                  }
                  case HOUR: {
                        simpleDateFormat.applyPattern ( "HH" );
                        return simpleDateFormat.format ( date );
                  }
                  case MILLISECOND: {
                        simpleDateFormat.applyPattern ( "SSS" );
                        return simpleDateFormat.format ( date );
                  }
                  case MINUTE: {
                        simpleDateFormat.applyPattern ( "mm" );
                        return simpleDateFormat.format ( date );
                  }
                  case MONTH: {
                        simpleDateFormat.applyPattern ( "MM" );
                        return simpleDateFormat.format ( date );
                  }
                  case SEASON: {
                        return mapGet ( date , Attr.seasonMAP , "MMdd" );
                  }
                  case SECOND: {
                        simpleDateFormat.applyPattern ( "ss" );
                        return simpleDateFormat.format ( date );
                  }
                  case WEEK: {
                        simpleDateFormat.applyPattern ( "EEE" );
                        return simpleDateFormat.format ( date );
                  }
                  case YEAR: {
                        simpleDateFormat.applyPattern ( "yyyy" );
                        return simpleDateFormat.format ( date );
                  }
                  case ZODIAC: {
                        simpleDateFormat.applyPattern ( "yyyy" );
                        Double year = Double.parseDouble ( simpleDateFormat.format ( date ) );
                        return Attr.lunarMap.get ( year % 12 );
                  }
            }
            return null;
      }

      /**
       *
       * @param period
       *
       * @return
       */
      public Map<Time , String> getFields ( Period period ) {
//      switch ( this.getType () ) {
//         case INT_CENTURY: {
//            throw new UnsupportedOperationException ( "Not supported yet." );
//         }
//         case INT_DAY: {
//            return utilGet ( period , 0.5 , Unit.DAY );
//         }
//         case INT_EANPN: {
//         }
//         case INT_ERA: {
//            throw new UnsupportedOperationException ( "Not supported yet." );
//         }
//         case INT_HOROSCOPE: {
//            return utilGet ( period , 1.0 , Unit.DAY );
//         }
//         case INT_HOUR: {
//            return utilGet ( period , 0.5 , Unit.HOUR );
//         }
//         case INT_MILLISECOND: {
//            throw new UnsupportedOperationException ( "Not supported yet." );
//         }
//         case INT_MINUTE: {
//            return utilGet ( period , 0.5 , Unit.MINUTE );
//         }
//         case INT_MONTH: {
//            return utilGet ( period , 0.5 , Unit.MONTH );
//         }
//         case INT_SESASON: {
//            return utilGet ( period , 1.0 , Unit.WEEK );
//         }
//         case INT_SECOND: {
//            return utilGet ( period , 0.5 , Unit.SECOND );
//         }
//         case INT_WEEK: {
//            return utilGet ( period , 1.0 , Unit.DAY );
//         }
//         case INT_YEAR: {
//            return utilGet ( period , 0.8 , Unit.MONTH );
//         }
//         case INT_ZODIAC: {
//            return utilGet ( period , 0.8 , Unit.MONTH );
//         }
//      }
            return null;
      }

//   private Map<Time , String> utilGet ( Period period , Double arg , Unit unit ) {
//      TimeUtil UTIL = TimeUtil.born ();
//      Map<Time , String> map = new TreeMap<> ();
//      Time[] dateList = UTIL.enu ( period.getStart () , period.getEnd () , arg , unit );
//      for ( Time date : dateList ) {
//         map.put ( date , date.tell ( this ) );
//      }
//      return map;
//   }
      private String mapGet ( AbstractTime date , Map<Integer[] , String> map , String regex ) {
            simpleDateFormat.applyPattern ( regex );
            Set<Integer[]> key = map.keySet ();
            for ( Integer[] minMax : key ) {
                  String strNum = simpleDateFormat.format ( date );
                  Integer intNum = Integer.parseInt ( strNum );
                  if ( Num.inRang ( minMax , intNum ) ) {
                        return map.get ( minMax );
                  }
            }
            return null;
      }

}
